package com.honey.mybatis.generator.mappper;

import com.honey.compilation.xml.Document;
import com.honey.compilation.xml.XmlElement;
import com.honey.core.dbmapping.introspect.IntrospectSchema;
import com.honey.core.dbmapping.introspect.IntrospectSchemaColumn;
import com.honey.core.types.FullyQualifiedJavaType;
import com.honey.mybatis.generator.MybatisPlugin;

public class DynamicConditionMapper extends AbstractMybatisMapper {
	
	public DynamicConditionMapper(MybatisPlugin belongPlugin) {
		super(belongPlugin);
	}
	public DynamicConditionMapper(MybatisPlugin belongPlugin,IntrospectSchema introspectSchema,IntrospectSchemaColumn introspectSchemaColumn) {
		super(belongPlugin, introspectSchema, introspectSchemaColumn);
	}
	
	public Document getDocument(){
		FullyQualifiedJavaType type = new FullyQualifiedJavaType(mybatisPlugin.getMapperTargetPackage(),"DynamicCondition$"+mybatisPlugin.getMapperfileSuffix());
		Document answer =  super.createMyBatisDocument(type , "dynamic.condition");
		XmlElement rootElement = answer.getRootElement();
		rootElement.addNewLine();
		rootElement.addNewLine();
		rootElement.addElement(getDefaultDynamicElement());
		rootElement.addNewLine();
		rootElement.addNewLine();
		rootElement.addElement(getUpdateDynamicElement());
		
		return answer ;
	}
	private XmlElement getDefaultDynamicElement(){
		XmlElement answer = new XmlElement("sql")
		.addAttribute("id", "defaultDynamic")
		.addXmlDoc("动态条件,用于动态组装SQL语句。")
		.addXmlDoc("其他的映射文件通过dynamic.condition.defaultDynamic引用。")
		;
		
		XmlElement choose = new XmlElement(
				new XmlElement(
						new XmlElement(
								new XmlElement(
										new XmlElement (
												new XmlElement (
														answer,
														"where"),
												"foreach")
												.addAttribute("collection", "oredCriteria")
												.addAttribute("item", "criteria")
												.addAttribute("separator", "OR"),
										"if")
										.addAttribute("test", "criteria.valid")
								,
								"trim"
						).addAttribute("prefix", "(")
						 .addAttribute("suffix", ")")
						 .addAttribute("prefixOverrides", "AND")
						,
						"foreach"
				).addAttribute("collection","criteria.criteria")
				.addAttribute("item","criterion")
				,
				"choose"
		) ;
		new XmlElement(choose,"when" )
		.addAttribute("test", "criterion.noValue")
		.addTextElement("AND ${criterion.condition}");
		
		new XmlElement(choose,"when" )
		.addAttribute("test", "criterion.singleValue")
		.addTextElement("AND ${criterion.condition} #{criterion.value}");
		
		new XmlElement(choose,"when" )
		.addAttribute("test", "criterion.betweenValue")
		.addTextElement("AND ${criterion.condition} #{criterion.value} AND #{criterion.secondValue}");
		
		new XmlElement(
				new XmlElement(choose,"when" )
					.addAttribute("test", "criterion.listValue")
					.addTextElement("AND ${criterion.condition}")
				,"foreach" 
		).addAttribute("collection","criterion.value")
		.addAttribute("item","listItem")
		.addAttribute("open","(")
		.addAttribute("close",")")
		.addAttribute("separator",",")
		.addTextElement("#{listItem}")
		;
		return answer ;
	}
	
	private XmlElement getUpdateDynamicElement(){
		XmlElement answer = new XmlElement("sql")
		.addAttribute("id", "updateDynamic")
		.addXmlDoc("动态条件,用于动态组装SQL语句。")
		.addXmlDoc("其他的映射文件通过dynamic.condition.updateDynamic引用。")
		;
		XmlElement choose = new XmlElement(
				new XmlElement(
						new XmlElement(
								new XmlElement(
										new XmlElement (
												new XmlElement (
														answer,
														"where"),
												"foreach")
												.addAttribute("collection", "example.oredCriteria")
												.addAttribute("item", "criteria")
												.addAttribute("separator", "OR"),
										"if")
										.addAttribute("test", "criteria.valid")
								,
								"trim"
						).addAttribute("prefix", "(")
						 .addAttribute("suffix", ")")
						 .addAttribute("prefixOverrides", "AND")
						,
						"foreach"
				).addAttribute("collection","criteria.criteria")
				.addAttribute("item","criterion")
				,
				"choose"
		) ;
		new XmlElement(choose,"when" )
		.addAttribute("test", "criterion.noValue")
		.addTextElement("AND ${criterion.condition}");
		
		new XmlElement(choose,"when" )
		.addAttribute("test", "criterion.singleValue")
		.addTextElement("AND ${criterion.condition} #{criterion.value}");
		
		new XmlElement(choose,"when" )
		.addAttribute("test", "criterion.betweenValue")
		.addTextElement("AND ${criterion.condition} #{criterion.value} AND #{criterion.secondValue}");
		
		new XmlElement(
				new XmlElement(choose,"when" )
					.addAttribute("test", "criterion.listValue")
					.addTextElement("AND ${criterion.condition}")
				,"foreach" 
		).addAttribute("collection","criterion.value")
		.addAttribute("item","listItem")
		.addAttribute("open","(")
		.addAttribute("close",")")
		.addAttribute("separator",",")
		.addTextElement("#{listItem}")
		;
		
		return answer ;
	}
}
